package com.je.app.model;


import java.util.Calendar;
import java.util.Date;
import java.util.HashSet;
import java.util.Set;

import javax.validation.constraints.AssertTrue;
import javax.validation.constraints.Min;
import javax.validation.constraints.NotNull;

import com.mysql.fabric.xmlrpc.base.Array;

@SuppressWarnings("serial")
public class Turno implements java.io.Serializable {

	private Integer idTurno;
	
	@NotNull
	private Sesion sesion;
	
	@NotNull
	private Habitacion habitacion;
	
	@NotNull
	private Date horaInicio;
	
	@NotNull
	private Date horaFin;
	
	@Min(0)
	private double montoHabitacion;
	
	@Min(0)
	private double montoConsumicion;
	
	private boolean terminado;
	
	private Set bajaConsumicions = new HashSet(0);

	@AssertTrue (message="La hora de finalizacion no puede ser anterior a la de inicio")//Valida que la fecha de fin sea posterior a la de inicio 
	private boolean isDateValid(){
		
		if(horaFin != null){
			return horaFin.after(horaInicio);	
		}
		
		return true;
		
	}
	
	public Turno() {
	}

	public Turno(Sesion sesion, Habitacion habitacion) { //VER SI HAY QUE ELIMINAR ESTE METODO
		//CALCULAR: fecha final, monto habitacion, 
		this.terminado = false;
		this.montoConsumicion = 0;
		this.sesion = sesion;
		this.habitacion = habitacion;
		this.horaInicio = new Date();
		this.habitacion.setEstado(EstadoHabitacion.OCUPADO);
		
		int hora = this.horaInicio.getHours();
		Calendar cal= Calendar.getInstance();
	    cal.setTime(this.horaInicio);
		int dia = cal.get(Calendar.DAY_OF_WEEK);
		long miliSeg = habitacion.getTipoHabitacion().getMinutosTiempoInicial(dia, hora)*1000*60; //1000 mseg -> 1 seg ; 60 seg -> 1 min
		this.horaFin = new Date(this.horaInicio.getTime()+miliSeg);
		
		//Calcula monto habitacion
		float cantHoras =  ((float)( horaFin.getTime() - horaInicio.getTime())/(float)(1000*60*60));
		cal= Calendar.getInstance();
	    cal.setTime(this.horaFin);
		dia = cal.get(Calendar.DAY_OF_WEEK);
		hora = this.horaFin.getHours();
		double precioHora = habitacion.getTipoHabitacion().getPrecioHora(dia,hora);
		this.montoHabitacion = Math.floor(precioHora * cantHoras * 100)/100;
		
		
		
	}

	public Turno(Sesion activeSesion, Habitacion habitacion, Date dateInicio,
			Integer duracionMinutos) {
		this.terminado = false;
		this.montoConsumicion = 0;
		this.sesion = activeSesion;
		this.habitacion = habitacion;
		this.horaInicio = dateInicio;
		this.habitacion.setEstado(EstadoHabitacion.OCUPADO);
		this.horaFin = new Date(horaInicio.getTime() + duracionMinutos * 60 *1000);
		
		//Calcula monto habitacion
		float cantHoras =  ((float)( horaFin.getTime() - horaInicio.getTime())/(float)(1000*60*60));
		Calendar cal= Calendar.getInstance();
	    cal.setTime(this.horaFin);
		int dia = cal.get(Calendar.DAY_OF_WEEK);
		int hora = this.horaFin.getHours();
		double precioHora = habitacion.getTipoHabitacion().getPrecioHora(dia,hora);
		this.montoHabitacion = Math.floor(precioHora * cantHoras * 100)/100;
	}

	public Integer getIdTurno() {
		return this.idTurno;
	}

	public void setIdTurno(Integer idTurno) {
		this.idTurno = idTurno;
	}

	public Sesion getSesion() {
		return this.sesion;
	}

	public void setSesion(Sesion sesion) {
		this.sesion = sesion;
	}

	public Habitacion getHabitacion() {
		return this.habitacion;
	}

	public void setHabitacion(Habitacion habitacion) {
		this.habitacion = habitacion;
	}

	public Date getHoraInicio() {
		return this.horaInicio;
	}

	public void setHoraInicio(Date horaInicio) {
		this.horaInicio = horaInicio;
	}

	public Date getHoraFin() {
		return this.horaFin;
	}

	public void setHoraFin(Date horaFin) {
		this.horaFin = horaFin;
	}

	public double getMontoHabitacion() {
		return this.montoHabitacion;
	}

	public void setMontoHabitacion(double montoHabitacion) {
		this.montoHabitacion = Math.floor(montoHabitacion * 100)/100;
	}

	public double getMontoConsumicion() {
		return this.montoConsumicion;
	}

	public void setMontoConsumicion(double montoConsumicion) {
		this.montoConsumicion = Math.floor(montoConsumicion * 100)/100;
	}

	public boolean isTerminado() {
		return this.terminado;
	}

	public void setTerminado(boolean terminado) {
		this.terminado = terminado;
	}

	public Set getBajaConsumicions() {
		return this.bajaConsumicions;
	}

	public void setBajaConsumicions(Set bajaConsumicions) {
		this.bajaConsumicions = bajaConsumicions;
	}

	@SuppressWarnings("unchecked")
	public void addConsumicion(BajaConsumicion consumicion){
		bajaConsumicions.add(consumicion);
		this.montoConsumicion += consumicion.getMontoTotal();
	}
	
	public void removeConsumicion(BajaConsumicion consumicion){
		bajaConsumicions.remove(consumicion);
		this.montoConsumicion -= consumicion.getMontoTotal();
		
	}
	
	public Object [] toArray() {
		Object [] array = new Object [10];
		String [] strings = this.horaInicio.toLocaleString().split(" "); 
		array [0] = strings[0];
		array [1] = this.habitacion.getNombre();
		array [2] = this.sesion.getUsuario().getNombre();
		array [3] = strings[1];
		strings = this.horaFin.toLocaleString().split(" ");
		array [4] = strings[1];
		Date tiempo = new Date(new Date().getTime() - this.horaInicio.getTime()-75600000) ;
		strings = tiempo.toLocaleString().split(" ");
		array [5] = strings[1];
		array [6] = this.montoHabitacion;
		array [7] = this.montoConsumicion;
		array [8] = this.montoHabitacion + this.montoConsumicion; 
		array [9] = this.idTurno;		
		return array;		 
		
	}
	
	public Object [] getArray() {
		Object [] array = new Object [7];
		array [0] = this.habitacion.getNombre();
		String [] strings = this.horaInicio.toLocaleString().split(" "); 
		array [1] = strings[1];
		strings = this.horaFin.toLocaleString().split(" ");
		array [2] = strings[1]; 
		array [3] = this.montoHabitacion;
		array [4] = this.montoConsumicion;
		array [5] = this.montoHabitacion + this.montoConsumicion;
	
				
		return array;		 
		
	}
	
	public Date getTimeLeft(){
		if(horaFin.after(new Date()))
		return new Date(horaFin.getTime()-new Date().getTime()-75600000);
		else return new Date(-75600000);
	}

	public String getTiempoTotal(){
		return new Date(horaFin.getTime()-horaInicio.getTime()-75600000).toLocaleString().split(" ")[1];
	}
	
	public void recalcularMontoHabitacion() {

		TipoHabitacion tipoHabitacion = habitacion.getTipoHabitacion();
		int hora = this.horaInicio.getHours();
		Calendar cal= Calendar.getInstance();
	    cal.setTime(this.horaInicio);
		int dia = cal.get(Calendar.DAY_OF_WEEK);
		
		cal= Calendar.getInstance();
	    cal.setTime(this.horaFin);
		dia = cal.get(Calendar.DAY_OF_WEEK);
		hora = this.horaFin.getHours();
		
		//Calcula monto habitacion
		float cantHoras =  ((float)( horaFin.getTime() - horaInicio.getTime())/(float)(1000*60*60));
		double precioHora = tipoHabitacion.getPrecioHora(dia,hora);
		this.montoHabitacion = Math.floor(precioHora * cantHoras * 100)/100;
	
	}

	public Object[] convertArray() {
		Object [] array = new Object [10];
		String [] strings = this.horaInicio.toLocaleString().split(" "); 
		array [0] = strings[0];
		array [1] = this.habitacion.getNombre();
		array [2] = this.sesion.getUsuario().getNombre() + " " + this.sesion.getUsuario().getApellido();
		array [3] = strings[1];
		strings = this.horaFin.toLocaleString().split(" ");
		array [4] = strings[1];
		array [5] = getTiempoTotal();
		array [6] = this.montoHabitacion;
		array [7] = this.montoConsumicion;
		array [8] = this.montoHabitacion + this.montoConsumicion; 
		array [9] = this.idTurno;		
		return array;
	}


}
